#include <iostream>
#include <vector>
#include <string>

using std::cout;
using std::endl;
using std::vector;
using std::string;

template <typename Container>
void display(const Container &con)
{
    for(auto &elem :  con)
    {
        cout << elem << "  ";
    }
    cout << endl;
}

void printVectorCapacity(const vector<int> &vec)
{
    cout << "size() = " << vec.size() << endl;
    cout << "capacity() = " << vec.capacity() << endl;
}

void test()
{
    cout << "sizeof(vector<int>) = " << sizeof(vector<int>) << endl;
    cout << "sizeof(vector<string>) = " << 
        sizeof(vector<string>) << endl << endl;

    vector<int> number = {1, 3, 5, 7, 9, 8, 6, 4, 2, 10};
    display(number);
    printVectorCapacity(number);

    cout << endl << "在vector的尾部进行插入与删除" << endl;
    number.push_back(200);
    number.push_back(300);
    display(number);
    printVectorCapacity(number);
    number.pop_back();
    display(number);
    printVectorCapacity(number);

    //为什么vector不支持在头部进行插入与删除？
    //原因：因为vector是一段开口的容器，头部是固定的，尾部是
    //开口的，那么如果在头部进行插入与删除，那么会导致后面的
    //所有元素进行移动,这样就会导致时间复杂度O(N)
    //
    //如何获取vector的第一个元素的地址?
    &number;//不能获取第一个元素的地址
    &number[0];//ok
    &*number.begin();//ok
    (long *)*(long *)&number;//ok

    cout << endl << "在vector的任意位置进行插入" << endl;
    auto it = number.begin();
    ++it;
    ++it;
    cout << "*it = " << *it << endl;
    number.insert(it, 300);
    display(number);
    cout << "*it = " << *it << endl;
    printVectorCapacity(number);

    cout << endl;
    it = number.begin();
    it += 2;
    cout << "*it = " << *it << endl;
    number.insert(it, 9, 666);
    display(number);
    cout << "*it = " << *it << endl;
    printVectorCapacity(number);

    //将这种情况称为迭代器失效（这是迭代器失效的一种形式）
    //原因：因为vector在进行insert操作的时候，有可能新插入的
    //元素的个数比较多，从而导致底层发生了扩容，但是迭代器还
    //指向老的空间的位置，然后再继续用该迭代器就会发生一些
    //意想不到的问题(就是会出现bug)
    //解决方法：不管迭代器上一次指到哪里，每次在使用迭代器之前
    //将迭代器重新置位（与新的空间之间产生关联即可）
    cout << endl;
    it = number.begin();
    it += 2;
    cout << "*it = " << *it << endl;
    vector<int> vec = {10, 30, 50, 20};
    number.insert(it, vec.begin(), vec.end());
    display(number);
    cout << "*it = " << *it << endl;
    printVectorCapacity(number);

    cout << endl;
    it = number.begin();
    it += 2;
    cout << "*it = " << *it << endl;
    number.insert(it, {11, 44, 77, 33});
    display(number);
    cout << "*it = " << *it << endl;
    printVectorCapacity(number);

    cout << endl << "vector元素的清空" << endl;
    number.clear();//清空
    number.shrink_to_fit();//回收多余空间
    cout << "size() = " << number.size() << endl;
    cout << "capacity() = " << number.capacity() << endl;
}

int main(int argc, char *argv[])
{
    test();
    return 0;
}

